package com.gongzonqiang.service.impl;

import java.util.ArrayList;
import java.util.List;
import java.util.Vector;

import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.gongzonqiang.exception.UserException;
import com.gongzonqiang.mapper.CollectionMapper;
import com.gongzonqiang.mapper.CommentMapper;
import com.gongzonqiang.mapper.MessageMapper;
import com.gongzonqiang.mapper.NoticeMapper;
import com.gongzonqiang.mapper.UserMapper;
import com.gongzonqiang.myenum.UserEnum;
import com.gongzonqiang.pojo.Category;
import com.gongzonqiang.pojo.Collection;
import com.gongzonqiang.pojo.Comment;
import com.gongzonqiang.pojo.Message;
import com.gongzonqiang.pojo.Notice;
import com.gongzonqiang.pojo.User;
import com.gongzonqiang.povo.CommentVo;
import com.gongzonqiang.povo.NoticeVo;
import com.gongzonqiang.service.NoticeService;
import com.gongzonqiang.service.UserService;

import tk.mybatis.mapper.entity.Example;
import tk.mybatis.mapper.entity.Example.Criteria;

@Service
@Transactional
public class UserServiceImpl implements UserService {
	
	@Autowired
	private UserMapper userMapper;
	@Autowired
	private NoticeMapper noticeMapper;
	@Autowired
	private CollectionMapper collectionMapper;
	@Autowired
	private CommentMapper commentMapper;
	@Autowired
	private MessageMapper messageMapper;
	@Autowired
	private NoticeService noticeService;
	
	/**
	 * 是否登录
	 * @param user 用户实体
	 * @return 
	 */
	public boolean isLogin(User user) {
		if(user == null) {
			//未登录
			throw new UserException(UserEnum.NOLOGIN);
		}
		
		return true;
	}
	
	/**
	 * 绑定手机号码
	 * @param user 用户实体(要被绑定的手机号码放在该实体中)
	 * @return 0失败 1成功
	 */
	public int bindingPhone(User user){
		//判断是否登录 不用判断 如果未登录就直接抛异常了
		isLogin(user);
		
		User user2 = new User();
		user2.setPhone(user.getPhone());
		
		//判断该手机号码是否被绑定
		if(userMapper.selectCount(user2)==1) {
			//抛出 手机号已被绑定的异常
			throw new UserException(UserEnum.PHONEBINDING);
		}
		
		//绑定手机号码 选用有Selective后缀的 属性为null时不做条件
		return userMapper.updateByPrimaryKeySelective(user);
	}
	
	/**
	 * 查看我发布的公告
	 * @param user 用户实体
	 * @Param pageNum 第几页
	 * @Param pageSize 几条数据
	 * @return 公告VO实体集合 包含分类（youjie）
	 */
	public PageInfo MyRelease(int pageNum,int pageSize,User user){
		isLogin(user);
		//获取我发布的公告数据
		Example example =new Example(Notice.class);
		Criteria createCriteria = example.createCriteria();
		createCriteria.andNotEqualTo("status", -2);
		createCriteria.andEqualTo("openid", user.getOpenid());
		//开启PageHelper
		PageHelper.startPage(pageNum, pageSize);
		PageInfo pageInfo = new PageInfo(noticeMapper.selectByExample(example));
		
		List<NoticeVo> list = new ArrayList<>();
		for(Notice notice2: (List<Notice>)pageInfo.getList()) {
			NoticeVo noticeVo = new NoticeVo();
			BeanUtils.copyProperties(notice2, noticeVo);
			Category category = noticeService.selectCategoryByCid(notice2.getCategoryId());
			noticeVo.setCategory(category);
			list.add(noticeVo);
		}
		
		pageInfo.setList(list);
		return pageInfo;
	}
	
	/**
	 * 查看我收藏的公告
	 * @param user
	 * @Param pageNum 第几页
	 * @Param pageSize 几条数据 
	 * @return 公告VO实体集合(分页)
	 */
	public PageInfo<NoticeVo> MyCollection(int pageNum,int pageSize,User user){
		isLogin(user);
		
		Collection collection = new Collection();
		collection.setOpenid(user.getOpenid());
		PageHelper.startPage(pageNum,pageSize);
		//查询出所有该用户收藏的公告的收藏信息 这里直接创建PageInfo是因为这个查询结果还会带一些其他数据,这里先保存起来,在后面换另一个集合
		PageInfo pageInfo = new PageInfo(collectionMapper.select(collection));
		List<NoticeVo> noticeVos = new Vector<NoticeVo>();
		
		
		//通过公告id获取公告信息 
		for(Collection collection2:(List<Collection>)pageInfo.getList()) {
			NoticeVo noticeVo = new NoticeVo();
			noticeVo.setCollectionId(collection2.getCollectionId());
			Notice notice = noticeMapper.selectByPrimaryKey(collection2.getNoticeId());
			//通过公告实体中用户编号获取发布公告用户的头像地址以及昵称
			User user2 = userMapper.selectByPrimaryKey(notice.getOpenid());
			// 分类
			Category category = noticeService.selectCategoryByCid(notice.getCategoryId());
			
			//我只要几个属性 不需要全部属性 所以我要手动设置该Vo的属性值
			noticeVo.setNoticeId(notice.getNoticeId());
			noticeVo.setContent(notice.getContent());
			noticeVo.setImg(notice.getImg());
			noticeVo.setBrowseNum(notice.getBrowseNum());
			noticeVo.setCollectionNum(notice.getCollectionNum());
			noticeVo.setForwardNum(notice.getForwardNum());
			noticeVo.setCreateDate(notice.getCreateDate());
			
			noticeVo.setHeadimg(user2.getHeadimg());
			noticeVo.setNickname(user2.getNickname());
			
			noticeVo.setCategory(category);
			noticeVos.add(noticeVo);
		}
		pageInfo.setList(noticeVos);
		
		return pageInfo;
	}
	
	/**
	 * 查看我的评论
	 * @param user
	 * @Param pageNum 第几页
	 * @Param pageSize 几条数据 
	 * @return 评论Vo实体集合(包含基本公告信息,发布公告用户头像和姓名,评论内容和评论时间)(分页)
	 */
	public PageInfo<CommentVo> MyComment(int pageNum,int pageSize,User user){
		isLogin(user);
		
		Notice notice = null;
		CommentVo commentVo = null;
		
		Comment comment = new Comment();
		comment.setOpenid(user.getOpenid());
		PageHelper.startPage(pageNum, pageSize);
		PageInfo pageInfo = new PageInfo(commentMapper.select(comment)); 	// 查询该用户所有评论
		
		List<CommentVo> commentVos = new Vector<CommentVo>();
		
		for(Comment comment2:(List<Comment>)pageInfo.getList()) {
			commentVo = new CommentVo();
			commentVo.setCommentId(comment2.getCommentId());
			//通过comment2中的公告id查到公告
			notice = noticeMapper.selectByPrimaryKey(comment2.getNoticeId());
			User user2 = userMapper.selectByPrimaryKey(notice.getOpenid());
			// 分类
			Category category = noticeService.selectCategoryByCid(notice.getCategoryId());
			
			//这个方法好像是接收方的属性已有属性值就不会覆盖
			BeanUtils.copyProperties(notice, commentVo);
			commentVo.setHeadimg(user2.getHeadimg());
			commentVo.setNickname(user2.getNickname());
			//评论内容和评论时间
			commentVo.setCommentContent(comment2.getContent());
			commentVo.setCommentCreateDate(comment2.getCreateDate());
			//公告分类
			commentVo.setCategory(category);
			
			commentVos.add(commentVo);
		}
		pageInfo.setList(commentVos);
		
		return pageInfo;
	}
	
	/**
	 * 查看消息通知(我发布的公告被评论了)
	 * @param user
	 * @Param pageNum 第几页
	 * @Param pageSize 几条数据
	 * @return 公告Vo实体集合(包含评论用户基本信息(编号,姓名,头像),基本公告信息)(分页)
	 */
	public PageInfo<NoticeVo> messageNotification(int pageNum,int pageSize,User user){
		isLogin(user);
		
		Message message = new Message();
		message.setOpenid(user.getOpenid());
		PageInfo pageInfo = new PageInfo(messageMapper.select(message));
		
		List<Notice> notices = new Vector<Notice>();
		
		for(Message message2:(List<Message>)pageInfo.getList()) {
			//通过消息通知获取到公告信息
			Notice notice2 = noticeMapper.selectByPrimaryKey(message2.getNoticeId());
			
			notices.add(notice2);
			//消息通知的目的已经达到(就是让用户知道自己发布的商品被评论了),然后删除掉这些消息通知
			messageMapper.deleteByPrimaryKey(message2.getMessageId());
		}
		pageInfo.setList(notices);
		
		return pageInfo;
	}
	
	/**
	 * 拉黑,解冻用户(禁止其登录,在登录时会判断)
	 * @param openId 用户编号
	 * @return 0失败 1成功
	 */
	public int freeze(String openId,int status){
		User user = new User();
		user.setOpenid(openId);
//		if(status!=-1||status!=1) {
//			throw new UserException(UserEnum.PARAMSFAIL);
//		}
		user.setStatus(status);
		
		return userMapper.updateByPrimaryKeySelective(user);
	}
	
	/**
	 * 用户列表(可依据的搜索条件:用户状态,用户昵称)
	 * @param user
	 * @Param pageNum 第几页
	 * @Param pageSize 几条数据 
	 * @return 用户实体集合
	 */
	public PageInfo<User> listUser(int pageNum,int pageSize,User user){
		
		Example example = new Example(User.class);
		Criteria criteria = example.createCriteria();
		if(user.getNickname()!=null&&!user.getNickname().equals("")) {
			criteria.andLike("nickname", "%"+user.getNickname()+"%");
		}
		if(user.getStatus()!=null&&!"".equals(user.getStatus())) {
			criteria.andEqualTo("status", user.getStatus());
		}
		if(user.getPhone()!=null&&!"".equals(user.getPhone())) {
			criteria.andLike("phone", "%"+user.getPhone()+"%");
		}
		
		PageHelper.startPage(pageNum,pageSize);
		
		return new PageInfo<User>(userMapper.selectByExample(example));
	}
	
	/**
	 * 查看用户发布的活动
	 * @param openId
	 * @Param pageNum 第几页
	 * @Param pageSize 几条数据 
	 * @return 公告实体集合
	 */
	public PageInfo<Notice> noticeByUser(int pageNum,int pageSize,String openId){
		Example example = new Example(Notice.class);
		//根据状态降序排列 1发布 0审核 -1不通过 -2用户删除
		example.setOrderByClause("status desc");
		Criteria createCriteria = example.createCriteria();
		createCriteria.andEqualTo("openid", openId);
		
		PageHelper.startPage(pageNum,pageSize);
		
		return new PageInfo<Notice>(noticeMapper.selectByExample(example));
	}
	
	/**
	 * 管理员登录(手机号码,密码)
	 * @param user
	 * @return 用户实体
	 */
	public User loginAdmin(User user){
		//增加条件:身份是否为管理员
		Example example = new Example(User.class);
		Criteria criteria = example.createCriteria();
		criteria.andEqualTo("phone",user.getPhone());
		criteria.andEqualTo("password",user.getPassword());
		criteria.andEqualTo("status",UserEnum.ADMIN.getCode());
		User dbUser = userMapper.selectOneByExample(example);
		if(dbUser==null) {
			throw new UserException(UserEnum.USERNAME_PWD_erro);
		}
		return dbUser;
	}
	
	/**
	 * 管理员修改密码(手机号码,密码)
	 * @param user
	 * @return 0失败 1成功
	 */
	public int updatePasswordAdmin(User user){
		return userMapper.updateByPrimaryKeySelective(user);
	}
	
	public boolean isAdmin(User user) {
		System.out.println(user.getStatus()+":"+"2".equals(user.getStatus()));
		isLogin(user);
		
		if(user.getStatus()!=2) {
			//不是管理员
			throw new UserException(UserEnum.NOTADMIN);
		}
		
		return true;
	}
	
	/**
	 * 根据用户openId获取用户信息
	 * @param openId
	 * @return 
	 * 	youjie
	 */
	@Override
	public User selectById(String openId) {
		return  userMapper.selectByPrimaryKey(openId);
	}
	/**
	 * 添加用户
	 * youjie
	 */
	@Override
	public int addUser(User user) {
		return userMapper.insert(user);
	}

}
